create type suite as object (
  name varchar2(30),
  
  prophecy_count_val integer,
  
  member function prophecy_count return integer,
  member function pass_count return integer,
  member function fail_count return integer,
  member procedure forsee(actual number, expected number_matcher),
  member procedure forsee(actual boolean, expected true_matcher),
  member procedure forsee(actual boolean, expected false_matcher),

  constructor function suite(name varchar2) return self as result
);
/

show errors type suite

create type body suite as
  member function prophecy_count return integer as
  begin
    return prophecy_count_val;
  end prophecy_count;
  
  member function pass_count return integer as
  begin
    return 0;
  end pass_count;
  
  member function fail_count return integer as
  begin
    return 0;
  end fail_count;
  
  member procedure forsee(actual number, expected number_matcher) as
  begin
    if not expected.matches(actual) then
      dbms_output.put_line(self.name || ' percieved that ' || actual || ' does not ' || expected.describe());
    end if;
  end forsee;

  member procedure forsee(actual boolean, expected true_matcher) as
  begin
    if not expected.matches(actual) then
      dbms_output.put_line(self.name || ' percieved not true');
    end if;
  end forsee;

  member procedure forsee(actual boolean, expected false_matcher) as
  begin
    if not expected.matches(actual) then
      dbms_output.put_line(self.name || ' percieved not false');
    end if;
  end forsee;

  constructor function suite(name varchar2) return self as result as
  begin
    self.name := name;
    return;
  end suite;
end;
/

show errors type body suite
